package bootstrap

import (
	"fmt"
	"github.com/astaxie/beego"
	"github.com/astaxie/beego/plugins/cors"
	"github.com/spf13/viper"
	"go-beego-api/component/ck_log"
	"go-beego-api/component/redis"
	"net/http"
	"net/url"

	"os"
	"os/signal"

	"go-beego-api/component/mysql"
	"go-beego-api/exception"
	"go-beego-api/exception/recover_func"

	"syscall"
	"time"

	"xorm.io/xorm/names"
)

// Init 初始化组件库 API
func Init(args ...string) {

	// 执行模式
	exception.RunMode = viper.GetString("app.http.mode")

	//初始化日志
	withStdout := viper.GetBool("log.stdout")
	ck_log.InitZap(withStdout)

	// mysql model for golint
	mysql.SetColumnMapper(names.GonicMapper{})

	//初始化MySQL数据库
	if viper.IsSet("mysql") {
		mysql.InitMySQL()

	}

	// 初始化es
	// elasticsearch.InitElasticSearchClient()

	// 初始化redis
	InitRedis()

}

func ApiInit() {
	// 创建HTTP代理
	proxyURL, _ := url.Parse("http://127.0.0.1:7890")
	http.DefaultTransport.(*http.Transport).Proxy = http.ProxyURL(proxyURL)

	workDir, _ := os.Getwd()
	viper.SetConfigName("application.yml")
	viper.SetConfigType("yml")
	viper.AddConfigPath(workDir + "/conf")
	viper.ReadInConfig()
	Init()

	// InitRabbitmq()
	//配置端口号
	beego.BConfig.Listen.HTTPPort = viper.GetInt("app.http.port")
	//配置运行模式
	beego.BConfig.CopyRequestBody = viper.GetBool("app.http.copyRequestBody")
	// 重置beego的recover方法
	beego.BConfig.RecoverPanic = true
	beego.BConfig.RecoverFunc = recover_func.RequestRecoverPanic
	beego.BConfig.RunMode = exception.RunMode

	beego.BConfig.WebConfig.AutoRender = false
	beego.BConfig.Log.AccessLogs = false
	beego.BConfig.Log.EnableStaticLogs = false
	beego.BConfig.Listen.Graceful = false
	CorsDomain()
	exception.SetDomain("GoBeegoApi")

}

func CorsDomain() {
	beego.InsertFilter("*", beego.BeforeRouter, cors.Allow(&cors.Options{
		AllowAllOrigins:  true,
		AllowMethods:     []string{"GET", "POST", "PUT", "DELETE", "OPTIONS"},
		AllowHeaders:     []string{"Origin", "Authorization", "Access-Control-Allow-Origin", "Access-Control-Allow-Headers", "Content-Type"},
		ExposeHeaders:    []string{"Content-Length", "Access-Control-Allow-Origin", "Access-Control-Allow-Headers", "Content-Type"},
		AllowCredentials: true,
	}))
}

// CommandInit 消费进程用的初始化
func CommandInit() {
	Init()

	// 初始化rabbitmq 后面废弃
	// InitRabbitmq()
}

// Run 启用webserver
func Run() {
	// 启动server
	go beego.Run()
	c := make(chan os.Signal, 1)

	// signal.Notify(c, syscall.SIGTERM)
	//signal.Notify(c, os.Interrupt, os.Kill, syscall.SIGUSR1, syscall.SIGUSR2, syscall.SIGTERM)
	signal.Notify(c, os.Interrupt, os.Kill, syscall.SIGTERM)
	s := <-c
	fmt.Println("stopping...Got signal:", s, time.Now().String())
	if exception.RunMode != exception.DEV {
		time.Sleep(30 * time.Second)
	}
}

func InitRedis() {
	host := viper.GetString("redis.default.host") + ":" + viper.GetString("redis.default.port")
	db := viper.GetInt("redis.default.db")
	auth := viper.GetString("redis.default.auth")
	idle := viper.GetInt("redis.default.pool.idle")
	redisOpt := redis.Options{
		MaxIdle:     idle,
		MaxActive:   10,
		Host:        host,
		PassWd:      auth,
		DB:          db,
		IdleTimeout: 180,
	}
	redis.InitRedis("default", redisOpt)
}
